﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using RaytracerLib.MathLib;
using System.Diagnostics;

namespace RaytracerLib.MathLib
{
    public static class RayMath
    {
        public static Vector3 Reflect(Vector3 a_in, Vector3 a_normal)
        {
            Debug.Assert(a_in.IsNormalized);
            Debug.Assert(a_normal.IsNormalized);

            return a_in - a_normal * (2 * a_in * a_normal);
        }

        public static Vector3 Mirror(Vector3 a_out, Vector3 a_normal)
        {
            Debug.Assert(a_out.IsNormalized);
            Debug.Assert(a_normal.IsNormalized);

            return a_out - a_normal * (2 * a_out * a_normal);
        }

        public static Vector3 Refract(Vector3 a_in, Vector3 a_normal, double a_n1, double a_n2,
            ref bool a_total_internal_reflection)
        {
            Debug.Assert(a_in.IsNormalized);
            Debug.Assert(a_normal.IsNormalized);
            Debug.Assert(a_n1 >= 1);
            Debug.Assert(a_n2 >= 1);

            double n = a_n1 / a_n2;
            double cos_alpha = -(a_in * a_normal);
            double cos_beta_2 = 1 - n * n * (1 - cos_alpha * cos_alpha);

            if (cos_beta_2 > 0)
                return n * a_in + (n * cos_alpha - Math.Sqrt(cos_beta_2)) * a_normal;
            else
            {
                a_total_internal_reflection = true;
                return Vector3.ZERO;
            }
        }

    }
}
